/**
 * Copyright 2010 Victor Egea Hernando
 *
 * RockScript is free software: you can redistribute it and/or modify
 * it under the terms of the GNU Lesser General Public License as published by
 * the Free Software Foundation, version 3 of the License.
 * 
 * RockScript is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU Lesser General Public License for more details.
 * 
 * You should have received a copy of the GNU Lesser General Public License
 * along with RockScript.  If not, see <http://www.gnu.org/licenses/>.
 */
#include "corelib.h"
 
namespace paper{

/****************************************************************************************
 * print
 ****************************************************************************************/
corelib::int32 print_hnd( paper::vmachine &vm, paper::method &mp, corelib::uint32 pc ){
	paper::__register &reg = vm.spreg( REG_TOOGLE(1) );

	if( !pc ){
		// print argument
		std::cout << ((ostring*)regobject(reg))->str();
	}else{
		// get string from object and print it!
	}
	return 1; // pc++
}

void print( vm_class &lib_class ){
	corelib::uint32 idx = 0;
	lib_class.get_method_idx( "mthd_1_print", idx );
	method *m_println = lib_class.get_method( idx );

	// allocate memory
	if(	!m_println->set_stack_frame_size( 0, 0 ) ){
		std::cout << "error allocating print memory" << std::endl;
		return;
	}

	m_println->set_cpp_handler(&print_hnd);
	m_println->set_flags(paper::FLG_MTHD_STATIC);
	m_println->add_inst_b(paper::OP_CPPCODE,0,0);
	m_println->add_inst_b(paper::OP_RETURN,10,0);
}

/****************************************************************************************
 * print a line
 ****************************************************************************************/
corelib::int32 print_line_hnd( paper::vmachine &vm, paper::method &mp, corelib::uint32 pc ){ 
	std::cout << std::endl;
	return 1; // pc++
}

void print_line( vm_class &lib_class ){
	corelib::uint32 idx, print_idx;
	lib_class.get_method_idx( "mthd_1_println", idx );
	method *m_println = lib_class.get_method( idx );

	lib_class.get_method_idx( "mthd_1_print", print_idx );

	// allocate memory
	if(	!m_println->set_stack_frame_size( 0, 0 ) ){
		std::cout << "error allocating println memory" << std::endl;
		return;
	}

	m_println->set_cpp_handler( &print_line_hnd );
	m_println->set_flags( paper::FLG_MTHD_STATIC );
	m_println->add_inst_a( paper::OP_LOADARG,1,1,0 );
	m_println->add_inst_b( paper::OP_KCCALL,print_idx,lib_class.idx() );
	m_println->add_inst_b(paper::OP_CPPCODE,0,0);
	m_println->add_inst_b(paper::OP_RETURN,10,0);
}

/****************************************************************************************
 * loads prompt class
 ****************************************************************************************/
void load_prompt_header( vmachine &vm ){
	// module class
	vm_class* lib_class;

	/****************************************************************** 
	 * corelib.Prompt
	 ******************************************************************/
	corelib::pair<paper::vm_class*, bool> testc = vm.add_class("corelib.Prompt");
	if(!testc.second){ return; } // check addition

	testc.first->add_method("print","mthd_1_");
	testc.first->add_method("println","mthd_1_");
}

void load_prompt_lib( vmachine &vm ){
	vm_class *lib_class = vm.get_class("corelib.Prompt").first;
	// define functions
	print( *lib_class );
	print_line( *lib_class );
}

}; // namespace paper;

